#ifndef __SCRIPT_FUNC_H__
#define __SCRIPT_FUNC_H__

#include <stdlib.h>
#include "script_var.h"
#include "TFly_list.h"
#include "script_stack.h"

struct exp_node_t;
struct script_code_block_t;
struct script_exec_block;
struct script_t;

/********************************************************
 *	内置C函数 类型
 *		返回值约定：  执行出错返回NULL. 如果函数无返回值
 *			返回一个 EXP_NODE_TYPE_CONST_NULL类型
 *		否则返回exp_node_t 指针。 
 *		返回值是一个新创建的exp_node_t结构体指针。
 *		返回的结构体会被销毁
 * ******************************************************/
typedef struct exp_node_t *(*script_c_func)(TFly_list_t *args,script_stack_t *block_stack,void *param);

/********************************************************
 *	内置C函数结构体
 *
 * ******************************************************/
typedef struct c_func{
    char			name[32];
	script_c_func	func;
	void			*param;
}c_func_t;

/********************************************************
 *	脚本函数结构体
 *
 * ******************************************************/
typedef struct script_func_t{
	char						*name;		// 函数名
	struct script_code_block_t	*block;		// 代码块

	//struct script_t				*script;	//	函数所属脚本
	struct script_exec_block *exec_block;

	// 参数列表	exp_node_t 指针  EXP_NODE_TYPE_CONST_STRING类型 
	// 保存变量名， 函数执行的时候创建变量到函数的block中
	TFly_list_t					*args;		
}script_func_t;

typedef enum{
	EXEC_FUNC_TYPE_C,		// 内置C函数
	EXEC_FUNC_TYPE_SCRIPT,	// 脚本定义函数
}exec_func_type_e;

typedef struct exp_func_node{
	exec_func_type_e type;			// 执行函数类型
	union{
		c_func_t		*c_func;	// 内置C函数
		script_func_t	*s_func;	// 脚本函数
	};
}exp_func_t;

/********************************************************
 *	执行函数结构体
 * ******************************************************/
typedef struct exec_func_node {
	char type;		// 0: exp_func_t; 1: exp_node_t
	union{
		struct exp_node_t *exp;
		exp_func_t *func;
	};
	TFly_list_t *args;			// 参数链表 参数类型:exp_node_t
}exec_func_t;

typedef struct exp_node_func{
	struct exp_node_t *exp;
	TFly_list_t *args;			// 参数链表 参数类型:exp_node_t
}exp_node_func_t;

struct exp_node_t *script_func_exec(exec_func_t *func, script_stack_t *block_stack);

void exp_func_destroy(exp_func_t *func);

exec_func_t *script_func_node_create(void);

/********************************************************
 *	function	script_c_func_register
 *		注册C函数到脚本中
 *
 *	@script		脚本指针
 *	@cfunc		c函数指针
 *	@func_name	函数名
 *	@param		函数参数
 *	
 *	return	
 *		成功 返回SCRIPT_ERR_NONE
 * ******************************************************/
int script_c_func_register(struct script_t *script,script_c_func cfunc, char *func_name,void *param);

int script_c_func_unregister(struct script_t *script, char *func_name);
int script_c_func_register_include(struct script_t *script,char *inc_var_name, script_c_func cfunc, char *func_name, void *param);

void script_func_node_destroy(exec_func_t *func);
void script_func_destroy(script_func_t *func);
int script_default_func_init(void);
exp_var_t *script_default_func_var_get(char *name);
void script_default_func_uninit(void);

/********************************************************
 *	function script_default_func_register
 *		默认函数注册
 * ******************************************************/
int script_default_func_register(script_c_func cfunc, char *func_name,void *param);

#endif
